﻿using Assistant.Forms.Configuration;
using Newtonsoft.Json;
using WebAssistant.BusinessLogic;
using WebAssistant.BusinessLogic.Model;
using Sunny.UI;
using System;
using System.Collections.Generic;
using System.Drawing.Printing;
using static WebAssistant.WinUI.UIInterFaceItem;
using WebAssistant.Common;
using PortaCapena.OdooJsonRpcClient;
using PortaCapena.OdooJsonRpcClient.Models;
using OdooRpcClient.Model.Base;
using PortaCapena.OdooJsonRpcClient.Consts;
using OdooRpcClient.Model.Product;
using System.Threading.Tasks;
using OdooRpcClient.Model.Account;

namespace Assistant.Forms
{
    public partial class FormSettings : UITitlePage
    {
        static OdooConfig config = new OdooConfig(
            apiUrl: "",
            dbName: "",
            userName: "",
            password: ""
            );
        static OdooClient odooClient = new OdooClient(config);
        public static FormSettings settingsPage;

        public FormSettings()
        {
            InitializeComponent();
            this.Load += ConfigLoaded;
            InitializeOdoo();
            settingsPage = this;
        }

        private void LinkLabel_SetLockScreenPassword_Click(object sender, EventArgs e)
        {
            try
            {
                if (DataAccess.CheckSettingExists("assistant.password")  )
                {
                    if(DataAccess.GetSettingByKey("assistant.password") == "")
                    {
                        FormSetLockScreenPassword frm = new FormSetLockScreenPassword();
                        frm.ShowDialog();
                        if (frm.IsOK)
                        {
                            //this.ShowSuccessDialog(frm.Person.ToString());
                        }

                        frm.Dispose();
                    }
                    else
                    {
                        FormChangeLockScreenPassword frm = new FormChangeLockScreenPassword();
                        frm.ShowDialog();
                        if (frm.IsOK)
                        {
                            //this.ShowSuccessDialog(frm.Person.ToString());
                        }

                        frm.Dispose();
                    }
                }
            }
            catch (Exception ex)
            {
                ShowErrorDialog("错误：" + ex.ToString());
            }
            
        }        

        private void ConfigLoaded(object sender, EventArgs e)
        {
            uiToolTip1.SetToolTip(lableURL, "例如：https://rainbow.rstudio.xyz" + '\n' + "注意末尾不需要 '/'",
                "提示", 61530, 32, WebAssistant.WinUI.Style.Helper.StyleToColor(this.Style));
            uiToolTip1.SetToolTip(labelPassword, "Odoo14及后续版本可以使用开发人员API密钥登录" + '\n' + "安全系数更高。",
                "提示", 61530, 32, WebAssistant.WinUI.Style.Helper.StyleToColor(this.Style));

            uiToolTip1.SetToolTip(lableSilentPrintingTip, "如果是提供给多个客户端访问，" + '\n' + "建议开启[静默打印]。",
                "提示", 61530, 32, WebAssistant.WinUI.Style.Helper.StyleToColor(this.Style));


            //数据库中的配置
            try
            {
                if (DataAccess.CheckSettingExists("assistant.log_retention_days"))
                    iud_LogRetentionDays.Value = Convert.ToInt32(DataAccess.GetSettingByKey("assistant.log_retention_days"));
                else
                    iud_LogRetentionDays.Value = 10;

                if (DataAccess.CheckSettingExists("assistant.auto_minimize"))
                    cb_AutoMinimize.Checked = Convert.ToBoolean(DataAccess.GetSettingByKey("assistant.auto_minimize"));
                else
                    cb_AutoMinimize.Checked = false;

                if (DataAccess.CheckSettingExists("odoo.server.url"))
                    tbServerUrl.Text = DataAccess.GetSettingByKey("odoo.server.url");
                else
                    tbServerUrl.Text = "";              

                if (DataAccess.CheckSettingExists("odoo.server.database"))
                    tbServerDB.Text = DataAccess.GetSettingByKey("odoo.server.database");
                else
                    tbServerDB.Text = "";

                if (DataAccess.CheckSettingExists("odoo.server.user"))
                    tbServerUsername.Text = DataAccess.GetSettingByKey("odoo.server.user");
                else
                    tbServerUsername.Text = "";

                if (DataAccess.CheckSettingExists("odoo.server.password"))
                    try
                    {
                        string password  = SecurityHelper.DecryptString(DataAccess.GetSettingByKey("odoo.server.password"), DataAccess.GetSettingByKey("odoo.key"));
                        tbServerPassword.Text = password;
                    }
                    catch(Exception ex)
                    {
                        ShowErrorDialog(ex.ToString());
                        tbServerPassword.Text = "";
                    }
                else
                    tbServerPassword.Text = "";

            }
            catch (Exception ex)
            {
                ShowErrorDialog("错误：" + ex.ToString());
            }
            checkboxUPSInstallationStatus.Checked = DataAccess.GetInterfaceIsInstalled("interface.printer.universal_printing_service");
            
            if (DataAccess.GetInterfaceIsInstalled("interface.printer.universal_printing_service"))
            {
                checkboxUPSInstallationStatus.Text = "已安装";                
                lableUPSList.Visible = true;
                listboxUPSPrinters.Visible = true;
                btnInstallUPS.Visible = false;

                lableUPSOptions.Visible = true;
                gbUPSOptions.Visible = true;
                checkSilentPrinting.Visible = true;
            }
            else
            {
                checkboxUPSInstallationStatus.Text = "未安装";
                lableUPSList.Visible = false;
                listboxUPSPrinters.Visible = false;
                btnInstallUPS.Visible = true;

                lableUPSOptions.Visible = false;
                gbUPSOptions.Visible = false;
                checkSilentPrinting.Visible = false;
            }

            bool upsIsConfigured = DataAccess.CheckPrinterExists("interface.printer.universal_printing_service");
            Printers printer = new Printers();
            if (upsIsConfigured)
            {
                printer = DataAccess.GetPrinterOptionsByKey("interface.printer.universal_printing_service");

                if (printer.Mode == 0)
                {
                    radioSystemPrinting.Checked = true;
                }
                else if (printer.Mode == 1)
                {
                    radioPrintPreview.Checked = true;
                }

                if (printer.Silent)
                {
                    checkSilentPrinting.Checked = true;
                }
                else
                {
                    checkSilentPrinting.Checked = false;
                }
            }
            foreach (string printerName in PrinterSettings.InstalledPrinters)//获取所有打印机名称
            {
                listboxUPSPrinters.Items.Add(printerName);
                if (upsIsConfigured)
                {
                    if (printerName == printer.Default)
                    {
                        //设置默认打印机
                        listboxUPSPrinters.SelectedIndex = listboxUPSPrinters.Items.IndexOf(printerName);
                    }
                }                
            }
        }

        private void InitializeOdoo()
        {
            string[] ConfigKeyList = new string[] {
                "odoo.server.url", "odoo.server.database", "odoo.server.user", "odoo.key", "odoo.server.password"
            };
            foreach (string configkey in ConfigKeyList)
            {
                if (!DataAccess.CheckSettingExists(configkey))
                {
                    //ShowWarningDialog("Odoo服务器配置错误！请设置。");
                    return;
                }
            }
            config = new OdooConfig(
                apiUrl: DataAccess.GetSettingByKey("odoo.server.url"),
                dbName: DataAccess.GetSettingByKey("odoo.server.database"),
                userName: DataAccess.GetSettingByKey("odoo.server.user"),
                password: SecurityHelper.DecryptString(DataAccess.GetSettingByKey("odoo.server.password"), DataAccess.GetSettingByKey("odoo.key"))
                );
            odooClient = new OdooClient(config);
        }
        
        private void btnSave_Click(object sender, EventArgs e)
        {          
            switch (uiTabControlMenu1.SelectedIndex)
            {
                case 0:
                    config = new OdooConfig(
                        apiUrl: tbServerUrl.Text,
                        dbName: tbServerDB.Text,
                        userName: tbServerUsername.Text,
                        password: tbServerPassword.Text
                        );
                    odooClient = new OdooClient(config);


                    string password_key = DataAccess.GetSettingByKey("odoo.key");

                    List<Settings> settings = new List<Settings>();
                    //settings.Clear();
                    Settings log_retention_days = new Settings("assistant.log_retention_days", iud_LogRetentionDays.Value.ToString());
                    Settings auto_minimize = new Settings("assistant.auto_minimize", cb_AutoMinimize.Checked.ToString());
                    Settings odoo_server_url = new Settings("odoo.server.url", tbServerUrl.Text);
                    Settings odoo_server_database = new Settings("odoo.server.database", tbServerDB.Text);
                    Settings odoo_server_user = new Settings("odoo.server.user", tbServerUsername.Text);
                    Settings odoo_server_password = new Settings("odoo.server.password", SecurityHelper.EncryptString(tbServerPassword.Text, password_key) );
                    
                    settings.Add(log_retention_days);
                    settings.Add(auto_minimize);
                    settings.Add(odoo_server_url);
                    settings.Add(odoo_server_database);
                    settings.Add(odoo_server_user);
                    settings.Add(odoo_server_password);//待处理加密密码

                    bool result = DataAccess.BatchUpdateInsertSetting(settings);

                    if (result)
                    {
                        ShowSuccessTip("设置保存成功！");
                    }
                    else
                    {
                        ShowErrorTip("设置保存失败！");
                    }
                    break;
                case 1:
 
                    string defaultPrinter = string.Empty;
                    int PrintingMode = 0;
                    bool UsingSilentPrinting = false;
                    
                    if (radioSystemPrinting.Checked)
                    {
                        PrintingMode = 0;
                    }
                    else if (radioPrintPreview.Checked)
                    {
                        PrintingMode = 1;
                    }

                    if (checkSilentPrinting.Checked)
                    {
                        UsingSilentPrinting = true;
                    }
                    else
                    {
                        UsingSilentPrinting = false;
                    }

                    if (listboxUPSPrinters.SelectedIndex == -1)
                    {
                        ShowWarningDialog("请选中默认打印机！");
                    }
                    else
                    {
                        defaultPrinter = listboxUPSPrinters.SelectedItem.ToString();
                        Printers printer = new Printers()
                        {
                            Key = "interface.printer.universal_printing_service",
                            Default = defaultPrinter,
                            Mode = PrintingMode,
                            Silent = UsingSilentPrinting,
                        };
                        var count = 0;
                        if (DataAccess.CheckPrinterExists("interface.printer.universal_printing_service"))
                        {
                            count = DataAccess.UpdatePrinterByKey("interface.printer.universal_printing_service", printer);
                        }
                        else
                        {
                            count = DataAccess.InsertPrinter(printer);
                        }

                        if (count > 0)
                        {
                            ShowSuccessTip("通用打印配置成功！");
                        }
                        else
                        {
                            ShowErrorTip("通用打印配置失败！");
                        }
                    }
                    
                    break;
                case 2:
                    //settings.Clear();
                    break;
     
            }            
        }

        private void btnCancel_Click(object sender, EventArgs e)
        {

        }

        #region "通用打印服务"
        private void btnInstallUPS_Click(object sender, EventArgs e)
        {
            Interfaces interfaces = new Interfaces() {
                Name = "通用打印服务",
                Category = UIInterFaceType.Printer,
                OS = OSType.Windows,
                Author = "RStudio",
                Website = "",
                Support = "rain.wen@outlook.com",
                Summary = "使用PC所连接的本地打印机进行打印",
                Description = "",
                Version = "1.0.0",
                Sequence = 1,
                Key = "interface.printer.universal_printing_service",
                State = false,
                AutoStart = false,
            };
            DateTime start = DateTime.Now;
            var result =  DataAccess.InstallInterface(interfaces);
            if (result > 0)
            {
                checkboxUPSInstallationStatus.Text = "已安装";
                checkboxUPSInstallationStatus.Checked = true;
                lableUPSList.Visible = true;
                listboxUPSPrinters.Visible = true;
                btnInstallUPS.Visible = false;

                lableUPSOptions.Visible = true;
                gbUPSOptions.Visible = true;
                checkSilentPrinting.Visible = true;

                DateTime end = DateTime.Now;
                Logs Log = new Logs()
                {
                    StartDate = start,
                    EndDate = end,
                    ServiceName = "通用打印接口",
                    MethodName = "Install",
                };

                FormHome.homePage.AddListViewItem(Log);
                WriteLog.Write(Log);

                FormMain.mainPage.BindInterfaceList();
                ShowSuccessTip("安装通用打印接口成功！");
            }
            else
            {
                ShowErrorTip("安装通用打印接口失败！");
            }
        }

        private void checkSilentPrinting_CheckedChanged(object sender, EventArgs e)
        {
            if (checkSilentPrinting.Checked)
            {
                gbUPSOptions.Enabled = false;
            }
            else
            {
                gbUPSOptions.Enabled = true;
            }
        }
        #endregion

        #region "同步Odoo基础数据"

        private bool SyncLanguageStatus = false;
        private bool SyncReportStatus = false;

        private async void btnSynchronizeBasicData_Click(object sender, EventArgs e)
        {
            ShowWaitForm();
            var loginResult = await odooClient.LoginAsync();
            if (loginResult.Failed)
            {
                HideWaitForm();
                ShowInfoDialog("登陆验证失败，请检查配置是否正确");
            }
            else
            {
                SetWaitFormDescription("正在同步数据，请稍后...");
                await SyncLanguageData();
                await SyncReportData();


                if (
                    SyncLanguageStatus && SyncReportStatus
                    )
                {
                    HideWaitForm();
                }
            }
        }

        private async Task SyncLanguageData()
        {            
            var langRepository = new OdooRepository<ResLangOdooModel>(config);
            langRepository.Config.Context.Language = "zh_CN";
            langRepository.Config.Context.Timezone = "AsiaChongqing";
            var langs = await langRepository.Query()
                .Select(x => new
                {
                    x.Id,
                    x.Name,
                    x.Code,
                    x.IsoCode,
                    x.UrlCode,
                    x.FlagImage,
                    x.FlagImageUrl,
                    x.Active,
                })
                .ToListAsync();
            if (langs.Succeed)
            {
                foreach (var lang in langs.Value)
                {
                    if (!DataAccess.CheckLanguagesExists(lang.Code))
                    {
                        Languages language = new Languages()
                        {
                            LanguageId = Convert.ToInt32(lang.Id),
                            Name = lang.Name,
                            Code = lang.Code,
                            IsoCode = lang.IsoCode,
                            UrlCode = lang.UrlCode,
                            FlagImage = StringHelper.GetWebImageBase64String(DataAccess.GetSettingByKey("odoo.server.url") + lang.FlagImageUrl),
                            FlagImageUrl = lang.FlagImageUrl,
                            Active = lang.Active != null && (bool)lang.Active,
                        };
                        DataAccess.InsertLanguage(language);
                    }
                }
                SyncLanguageStatus = true;
            }
            else
            {
                ShowErrorTip("同步语言错误");
            }
        }

        private async Task SyncReportData()
        {
            var reportRepository = new OdooRepository<IrActionsReportOdooModel>(config);
            reportRepository.Config.Context.Language = "zh_CN";
            reportRepository.Config.Context.Timezone = "AsiaChongqing";
            var reports = await reportRepository.Query()
                .Where(x => x.UseAssistant, OdooOperator.EqualsTo, true)
                .Select(x => new
                {
                    x.Name,
                    x.Id,
                    x.Model,
                    x.ReportName,
                    x.UseAssistant,
                    x.AssistantRdlTemplate,
                    x.AssistantDataTemplate
                })
                .ToListAsync();
            if (reports.Succeed)
            {
                List<Reports> InsertList = new List<Reports>();
                List<Reports> UpdateList = new List<Reports>();
                List<Reports> reportList = new List<Reports>();

                foreach (var report in reports.Value)
                {
                    Reports rp = new Reports
                    {
                        Name = report.Name,
                        ReportId = Convert.ToInt32(report.Id),
                        ReportName = report.ReportName,
                        Model = report.Model,
                        ReportTemplate = report.AssistantRdlTemplate,
                        DataTemplate = report.AssistantDataTemplate,
                        UseAssistant = report.UseAssistant
                    };
                    reportList.Add(rp);
                }
                try
                {
                    var result = DataAccess.BatchUpdateInsertReport(reportList);
                    ShowInfoNotifier(result.ToString() + "条报表记录同步成功！");
                }
                catch (Exception ex)
                {
                    ShowErrorNotifier("报表记录失败:" + ex.ToString());
                }

                SyncReportStatus = true;
            }
            else
            {
                ShowErrorTip("同步报表数据错误");
            }
        }

        #endregion

    }
}
